package ClientSide;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.InetAddress;
import java.net.Socket;
import java.net.UnknownHostException;
import java.util.StringTokenizer;

import javax.swing.JList;
import javax.swing.JTextArea;

import Handlers.ClientHandler;

/**
 * @author Avishai Kopeliansky 
 * @ID 066717752
 * @author David Shimshon
 * @ID 038185617
 */
public class Client extends Thread {
	private String name,address,port;
	private PrintWriter out;
	private BufferedReader in;
	private Socket sock;
	private boolean flag = true;
	private boolean isOK;
	private JTextArea jta;
	private JList<String> list;

	/**
	 * @param name Nickname
	 * @param address Server Address
	 * @param port Server Pot
	 * @param jt TextArea to append text
	 * @param list Chat users list
	 */
	public Client(String name, String address, String port, JTextArea jt, JList<String> list){
		this.name = name;
		this.address = address;
		this.port = port;
		this.jta = jt;	
		this.list = list;
		isOK = false;
	}

	/**
	 * Initializes the socket connection, the OutStream Writer, and the input Stream reader
	 */
	public void initMe(){
		try {
			this.sock = new Socket(InetAddress.getByName(address),Integer.parseInt(port));				
			this.out = new PrintWriter(sock.getOutputStream(),true);				
			this.in = new BufferedReader(new InputStreamReader(sock.getInputStream()));		
			isOK = this.sock.isConnected();
		}

		catch(UnknownHostException e){
			e.printStackTrace();
		}
		catch(IOException e){
			e.printStackTrace();
		}
	}


	/**
	 * @return true if connection succeeded 
	 */
	public boolean isOk(){
		return this.isOK;
	}
	public void run(){			
		String inc = "";
		
		ClientHandler ch = new ClientHandler();
		ch.join(this);
		try{
			while(this.flag)
			{
				try
				{
					inc = this.in.readLine();
					StringTokenizer st = new StringTokenizer(inc, "<>");
					String tmp = "";
					if (st.hasMoreTokens()) {
						tmp = st.nextToken();
						if(st.hasMoreTokens()){						
						ch.sorter(tmp, st.nextToken(),out, jta, list);
						}
						else
							ch.sorter(tmp, tmp, out, jta, list);
							
						
					}
					this.jta.setCaretPosition(jta.getDocument().getLength());
				}
				catch (IOException e)
				{
					e.printStackTrace();
				}

			}

		}
		catch(Exception e){ 
			e.printStackTrace();
			System.out.println("Prob");};
	}

	/**
	 * Construct the personal Message and dispatch it
	 * @param s for the message
	 * @param name for the personal message recipient 
	 */
	public void writeMsg(String s, String name){
		String t = ClientHandler.getPM(name, this.name, s);
		this.out.println(t);
	}
	/**
	 * Construct the message to broadcast and dispatch it
	 * @param s message to broadcast
	 */
	public void writeMsg(String s){
		String t = ClientHandler.getUM(this.name, s);
		this.out.println(t);
		System.out.println("written:"+t);
	}
	/**
	 *  Ask the Server to authenticate
	 */
	public void auth(){
		this.out.println(ClientHandler.auth(this.name));
	}

	/**
	 *  Close the connection from the server side and from client side
	 */
	public void close(){
		this.out.println("Disconnect");
		this.flag = false;
	}
	
	/**
	 * @return True if can run, False if not
	 */
	public boolean getFlag(){
		return this.flag;
	}
	
	/**
	 * Change Name
	 * @param s new name
	 */
	public void setNames(String s){
		this.name = s;
	}
	
}

